/**
 * 日期格式化函数（原生实现）
 * @param {Date|string|number} date - 可被new Date()解析的日期
 * @param {string} format - 格式字符串，默认'YYYY-MM-DD HH:mm:ss'
 * @returns {string} 格式化后的日期字符串
 */
function formatDate(date = new Date(), format = "YYYY-MM-DD HH:mm:ss") {
  // date  可被new Date()解析的日期
  const d = new Date(date)
  if (isNaN(d.getTime())) {
    throw new Error("无效日期")
  }

  const padZero = (num) => (num < 10 ? `0${num}` : num)
  const replacements = {
    YYYY: d.getFullYear(),
    MM: padZero(d.getMonth() + 1),
    DD: padZero(d.getDate()),
    HH: padZero(d.getHours()),
    mm: padZero(d.getMinutes()),
    ss: padZero(d.getSeconds()),
    SSS: d.getMilliseconds().toString().padStart(3, 0),
  }

  return format.replace(
    /YYYY|MM|DD|HH|mm|ss|SSS/g,
    (match) => replacements[match]
  )
}

// 使用示例
console.log(formatDate()) // 当前时间，如 2025-06-26 19:44:48
console.log(formatDate("2023-05-20", "YYYY/MM/DD")) // 2023/05/20
console.log(formatDate(1684567890000, "YYYY年MM月DD日 HH时mm分")) // 2023年05月20日 14时31分

// replace(pattern, replacement)
// pattern
// 可以是字符串或者一个带有 Symbol.replace 方法的对象，典型的例子就是正则表达式。任何没有 Symbol.replace 方法的值都会被强制转换为字符串。

// replacement
// 可以是字符串或函数。

// 如果是字符串，它将替换由 pattern 匹配的子字符串。支持一些特殊的替换模式，请参阅下面的指定字符串作为替换项部分。
// 如果是函数，将为每个匹配调用该函数，并将其返回值用作替换文本。下面的指定函数作为替换项部分描述了提供给此函数的参数。

// 使用dayjs
const dayjs = require("dayjs")
function formatDateWithDayjs(
  date = new Date(),
  format = "YYYY-MM-DD HH:mm:ss"
) {
  const d = dayjs(date)
  if (!d.isValid()) {
    throw new Error("Invalid date")
  }
  return d.format(format)
}

// 使用示例
console.log(formatDateWithDayjs()) // 当前时间 2025-06-26 19:49:36
console.log(formatDateWithDayjs("2025-05-20", "YYYY/MM/DD")) // 2025/05/20
console.log(formatDateWithDayjs(1656767890000, "YYYY年MM月DD日 HH时mm分")) // 2022年07月02日 21时18分
